package com.yanfei.zero.infrastructure.config;

import java.util.HashMap;
import java.util.Map;

import org.springframework.amqp.core.Binding;
import org.springframework.amqp.core.BindingBuilder;
import org.springframework.amqp.core.Queue;
import org.springframework.amqp.core.TopicExchange;
import org.springframework.amqp.rabbit.connection.CachingConnectionFactory;
import org.springframework.amqp.rabbit.connection.ConnectionFactory;
import org.springframework.amqp.rabbit.core.RabbitAdmin;
import org.springframework.beans.BeansException;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.beans.factory.config.BeanPostProcessor;
import org.springframework.context.annotation.Bean;
import org.springframework.stereotype.Component;

@Component
public class DirectRabbitConfig implements BeanPostProcessor {
	
    @Value("${spring.rabbitmq.host}")
    private String host;
    @Value("${spring.rabbitmq.port}")
    private int port;
    @Value("${spring.rabbitmq.username}")
    private String username;
    @Value("${spring.rabbitmq.password}")
    private String password;
	
    /**
     * RabbitMQ的TOPIC_EXCHANGE交换机名称
     */
    public static final String TOPIC_EXCHANGE_DEMO_NAME = "topic.exchange.demo.name";
    
    public static final String TOPIC_EXCHANGE_DEAD = "topic.exchange.dead";
    /**
     * RabbitMQ的TOPIC_EXCHANGE交换机的队列A的名称
     */
    public static final String TOPIC_EXCHANGE_QUEUE_A = "topic.queue.a";

    /**
     * RabbitMQ的TOPIC_EXCHANGE交换机的队列B的名称
     */
    public static final String TOPIC_EXCHANGE_QUEUE_B = "topic.queue.b";

    /**
     * RabbitMQ的TOPIC_EXCHANGE交换机的队列C的名称
     */
    public static final String TOPIC_EXCHANGE_QUEUE_C = "topic.queue.c";
    
    @Bean
    public TopicExchange rabbitmqDemoTopicExchange() {
        //配置TopicExchange交换机
        return new TopicExchange(TOPIC_EXCHANGE_DEMO_NAME, true, false);
    }
    
    /**
     * 死信交换机
     */
    @Bean
    TopicExchange deadExchange() {
        return new TopicExchange(TOPIC_EXCHANGE_DEAD, true, false);
    }

    


    @Bean
    public Queue topicExchangeQueueA() {
        //创建队列1
    	Map<String, Object> arguments = new HashMap<String, Object>();
   	    // 绑定该队列到死信交换机
	   	arguments.put("x-dead-letter-exchange", TOPIC_EXCHANGE_DEAD);
	   	arguments.put("x-dead-letter-routing-key", "deadRouting");
        return new Queue(TOPIC_EXCHANGE_QUEUE_A, true, false, false,arguments);
    }

    @Bean
    public Queue topicExchangeQueueB() {
        //创建队列2
    	Map<String, Object> arguments = new HashMap<String, Object>();
    	 // 绑定该队列到死信交换机
    	arguments.put("x-dead-letter-exchange", TOPIC_EXCHANGE_DEAD);
    	arguments.put("x-dead-letter-routing-key", "deadRouting");
    	 // 队列设置最大长度
    	arguments.put("x-max-length", 5);
    	
        // 队列设置消息过期时间 3 秒  代码中尽量使用 消息TTL，不要用 队列TTL。
    	arguments.put("x-message-ttl", 3 * 1000);
        return new Queue(TOPIC_EXCHANGE_QUEUE_B, true, false, false,arguments);
    }

    @Bean
    public Queue deadQueueC() {
        //创建队列3 死信队列
        return new Queue(TOPIC_EXCHANGE_QUEUE_C, true, false, false);
    }

    @Bean
    public Binding bindTopicA() {
        //队列A绑定到FanoutExchange交换机
        return BindingBuilder.bind(topicExchangeQueueA())
                .to(rabbitmqDemoTopicExchange())
                .with("a.*");
    }

    @Bean
    public Binding bindTopicB() {
        //队列A绑定到FanoutExchange交换机
        return BindingBuilder.bind(topicExchangeQueueB())
                .to(rabbitmqDemoTopicExchange())
                .with("b.*");
    }

    @Bean
    public Binding deadRouteBinding() {
        return BindingBuilder.bind(deadQueueC())
                .to(deadExchange())
                .with("deadRouting");
    }
    
    
    @Override
    public Object postProcessAfterInitialization(Object bean, String beanName) throws BeansException {

        return null;
    }
    
    @Bean
    public ConnectionFactory connectionFactory() {
        //注入并配置ConnectionFactory
        CachingConnectionFactory connectionFactory = new CachingConnectionFactory();
        connectionFactory.setHost(host);
        connectionFactory.setPort(port);
        connectionFactory.setUsername(username);
        connectionFactory.setPassword(password);
        connectionFactory.setVirtualHost("/");
        return connectionFactory;
    }
    @Bean  
    public RabbitAdmin rabbitAdmin(ConnectionFactory connectionFactory) {  
        RabbitAdmin rabbitAdmin = new RabbitAdmin(connectionFactory);
    	//启动项目即创建交换机和队列
        rabbitAdmin.declareExchange(rabbitmqDemoTopicExchange());
        rabbitAdmin.declareExchange(deadExchange());
        rabbitAdmin.declareQueue(topicExchangeQueueA());
        rabbitAdmin.declareQueue(topicExchangeQueueB());
        rabbitAdmin.declareQueue(deadQueueC());
        return rabbitAdmin;  
    }  
    
}